1 00:00:00,560 --> 00:00:05,750 In this lecture, we're going to be creating bullet holes that will appear on any surface that is hit 2 00:00:05,750 --> 00:00:06,530 by our bullets. 3 00:00:06,530 --> 00:00:12,230 So if I pull out my gun and I shoot, as you can see, bullet holes appear at where our bullets hit. 4 00:00:12,230 --> 00:00:17,960 And then if I pull out my shotgun and shoot, as you can see, there is the spread from all of the pellets 5 00:00:17,960 --> 00:00:19,760 shot out of our shotgun. 6 00:00:22,280 --> 00:00:23,960 So let's get started. 7 00:00:24,840 --> 00:00:26,760 Back inside of our guns handler script. 8 00:00:26,760 --> 00:00:30,510 Let's go ahead and create a function for creating a bullet hole. 9 00:00:30,510 --> 00:00:33,330 I'll call this function create bullet hole. 10 00:00:33,830 --> 00:00:37,490 And we can get past the properties for a particular gun. 11 00:00:37,490 --> 00:00:41,210 So that way we set the size of the bullet hole to the correct size. 12 00:00:41,210 --> 00:00:47,480 And then we also want to grab the result or that raycast information from the client side raycast. 13 00:00:47,630 --> 00:00:49,760 Then we can go ahead and check in this function. 14 00:00:49,760 --> 00:00:51,590 If there is a raycast result. 15 00:00:51,590 --> 00:00:55,970 If there is no result, then we're just going to return because there's nothing to create a bullet hole 16 00:00:55,970 --> 00:00:56,510 on. 17 00:00:56,510 --> 00:01:01,100 Otherwise we can go ahead and get that instance that we hit, which is going to be equal to our result 18 00:01:01,130 --> 00:01:03,950 dot raycast result and get that instance. 19 00:01:04,510 --> 00:01:06,970 And then we can go ahead and create a new bullet hole. 20 00:01:07,480 --> 00:01:11,920 And that's going to be inside of replicated storage, shared parts. 21 00:01:11,920 --> 00:01:15,040 And our bullet hole is inside of there and we're going to clone that. 22 00:01:15,970 --> 00:01:21,310 And then we're going to make sure to un anchor our bullet hole, because we want to weld this bullet 23 00:01:21,310 --> 00:01:22,960 hole to whatever part it hit. 24 00:01:22,960 --> 00:01:28,870 That way, if the part that we hit belongs to a limb of another character model, that bullet hole will 25 00:01:28,870 --> 00:01:30,640 move along with that limb. 26 00:01:30,640 --> 00:01:34,840 So we'll also create a new weld here instance dot new weld constraint. 27 00:01:35,110 --> 00:01:38,710 And then part zero for the weld is going to be equal to our bullet hole. 28 00:01:38,710 --> 00:01:44,020 And then the part one for our weld is going to be equal to the instance we hit. 29 00:01:44,830 --> 00:01:48,940 Then we can go ahead and set the parent of the weld equal to the bullet hole. 30 00:01:49,720 --> 00:01:56,380 And now what we want to do is we want to go ahead and get the offset between the position of our instance 31 00:01:56,380 --> 00:01:58,300 and where we hit on our instance. 32 00:01:58,300 --> 00:02:02,740 So if you remember, the client sends us information of where the position of the instance was. 33 00:02:02,740 --> 00:02:07,540 And then we also get past the information of where exactly we ray casted and hit a point at. 34 00:02:07,540 --> 00:02:08,830 So I'm going to create a variable. 35 00:02:08,830 --> 00:02:10,090 I'm going to call it offset. 36 00:02:10,090 --> 00:02:15,070 And it's going to be equal to my result dot raycast result dot position. 37 00:02:15,070 --> 00:02:18,820 And I'm going to subtract this by my result dot instance position. 38 00:02:18,820 --> 00:02:24,850 That way I'm getting this offset between the position of my instance and where we hit. 39 00:02:24,850 --> 00:02:30,940 And then using this offset we can go ahead and calculate where we should position our bullet hole based 40 00:02:30,940 --> 00:02:33,430 on the position of the instance on the server. 41 00:02:33,430 --> 00:02:36,910 So we're going to call this our server key frame offset. 42 00:02:36,910 --> 00:02:39,700 And that's going to be equal to a key frame dot new. 43 00:02:40,350 --> 00:02:43,050 And the position is going to be the instance position. 44 00:02:43,050 --> 00:02:50,250 But then we also want to add a key frame that's going to be the offset that we just calculated right 45 00:02:50,250 --> 00:02:50,520 here. 46 00:02:50,520 --> 00:02:52,230 So key frame dot new. 47 00:02:52,230 --> 00:02:55,350 And we're going to calculate it with this offset. 48 00:02:55,380 --> 00:03:00,720 Now that we have the position where we should set our bullet hole, we can go ahead and update the properties 49 00:03:00,720 --> 00:03:01,560 of our bullet hole. 50 00:03:01,560 --> 00:03:06,930 For example we can update the size to be equal to the properties dot bullet hole size. 51 00:03:07,260 --> 00:03:11,400 And then we can also update the key frame of our bullet hole to be equal to. 52 00:03:11,400 --> 00:03:13,410 And we're going to create a new key frame. 53 00:03:14,490 --> 00:03:18,240 And it's going to be at our server keyframe offset position. 54 00:03:18,240 --> 00:03:22,860 And I want this keyframe to be looking in a particular direction. 55 00:03:22,860 --> 00:03:27,660 And the direction that I want the bullet to look at needs to be the same normal vector of the face we 56 00:03:27,690 --> 00:03:28,020 hit. 57 00:03:28,020 --> 00:03:35,280 For example, if we were to hit, let's say this part right here, then I want to match up the rotation 58 00:03:35,280 --> 00:03:38,430 of our bullet hole to be flush or parallel with the surface. 59 00:03:38,430 --> 00:03:43,200 So you can imagine the normal vector for this face right here is going to be pointing out this way. 60 00:03:43,200 --> 00:03:49,740 So I want the keyframe of my bullet hole to be set at that position, while also looking in that direction 61 00:03:49,740 --> 00:03:51,300 of the normal vector. 62 00:03:51,510 --> 00:03:53,310 And that's going to be very easy to do. 63 00:03:53,340 --> 00:03:56,400 We can use actually the look at. 64 00:03:57,390 --> 00:03:58,470 Function. 65 00:03:58,470 --> 00:04:03,600 And where we want to look at is going to be at our server C frame offset dot position. 66 00:04:03,600 --> 00:04:11,040 And then we want to offset this position by the result dot raycast result dot normal. 67 00:04:11,280 --> 00:04:19,410 So you can imagine this is a new position that is one stud in front of where we hit at our raycast and 68 00:04:19,410 --> 00:04:24,090 the direction of wherever our face that we hit is looking towards. 69 00:04:24,420 --> 00:04:29,160 So now that we've set the bullet hole at the correct position, we can go ahead and set the parent of 70 00:04:29,160 --> 00:04:34,470 the bullet hole, and I'm going to place it in the workspace dot filtering folder, and I'm going to 71 00:04:34,470 --> 00:04:36,180 put it in the bullet holes folder. 72 00:04:37,080 --> 00:04:41,730 Then the other thing I actually want to do is I want to go ahead and update the color of my bullet hole 73 00:04:41,760 --> 00:04:45,030 to match the color of whatever part it hit. 74 00:04:45,300 --> 00:04:49,650 So, in fact, inside of the bullet hole, we're going to find the decal that's in there. 75 00:04:49,650 --> 00:04:52,050 So find First Child which is a decal. 76 00:04:52,050 --> 00:04:58,350 And we want to update the color three of this decal to be equal to the instance dot color. 77 00:04:58,890 --> 00:05:03,090 Then once we do that, we can go ahead and emit some particles out of our bullet hole. 78 00:05:03,090 --> 00:05:06,030 So bullet hole we'll get the particle emitter. 79 00:05:06,300 --> 00:05:11,760 And we're going to firstly update the color of the particles as well to match the color of the instance. 80 00:05:11,760 --> 00:05:15,210 So we're going to make a new color sequence dot new. 81 00:05:15,210 --> 00:05:17,520 And we're going to pass the instance dot color. 82 00:05:17,970 --> 00:05:22,500 And then for the bullet hole dot particle emitter we're going to emit. 83 00:05:23,270 --> 00:05:25,250 According to the properties. 84 00:05:25,250 --> 00:05:26,780 Dot bullet hole. 85 00:05:26,780 --> 00:05:28,340 Particle amount. 86 00:05:32,260 --> 00:05:35,230 And just like that, we have our bullet hole complete. 87 00:05:35,680 --> 00:05:38,620 Now, we don't want those bullet hole to remain on the map forever. 88 00:05:38,620 --> 00:05:42,490 So what we can go ahead and do is actually grab the debris service. 89 00:05:42,820 --> 00:05:45,040 So debris equal game get service debris. 90 00:05:45,490 --> 00:05:49,870 And then we can go ahead and clean up this bullet hole off of the map after a set period of time. 91 00:05:49,870 --> 00:05:54,190 So we're going to add an item to the debris service. 92 00:05:54,190 --> 00:05:56,530 And the item is going to be our bullet hole. 93 00:05:56,530 --> 00:06:00,700 And we can go ahead and wait for maybe I don't know something like 10s. 94 00:06:00,700 --> 00:06:04,510 So after 10s the bullet hole will disappear and be destroyed. 95 00:06:05,440 --> 00:06:11,320 Now that we have our function complete, we can go ahead and call our function from our shoot function. 96 00:06:11,350 --> 00:06:17,680 So when we calculate the damage, we also want to go ahead and create a bullet hole for a pellet. 97 00:06:17,680 --> 00:06:21,490 So we'll pass the properties and then the pellet result. 98 00:06:22,000 --> 00:06:24,340 And then we want to do the same thing down here. 99 00:06:24,550 --> 00:06:32,560 We're going to create a bullet hole pass the properties as well as the args which is the result. 100 00:06:33,340 --> 00:06:39,880 So now if we go and play test our game and we are to shoot our guns, we should see a bullet hole appear 101 00:06:39,880 --> 00:06:41,920 at wherever we shot. 102 00:06:42,430 --> 00:06:45,190 And let's say I shoot right there and I click. 103 00:06:45,310 --> 00:06:47,950 As you can see now, our bullet hole has appeared. 104 00:06:47,950 --> 00:06:52,030 And as you can see, it's also flush or parallel with the surface that we hit right here. 105 00:06:52,030 --> 00:06:53,500 It's matching the Or. 106 00:06:53,500 --> 00:06:56,530 It's looking towards the normal vector of this face. 107 00:06:56,530 --> 00:07:00,670 And then you can see it disappeared as well because the debris service cleaned it up for us. 108 00:07:00,670 --> 00:07:02,650 And again we can shoot any surface. 109 00:07:02,650 --> 00:07:07,840 And as you can see the bullet holes are matching the normal vector of the surface they're hitting. 110 00:07:10,190 --> 00:07:13,550 I can also shoot some other stuff, for example, this bench with my shotgun. 111 00:07:13,550 --> 00:07:14,360 So if I click. 112 00:07:15,170 --> 00:07:20,480 As you can see, each of our individual pellets flew out of our shotgun and hit the different parts 113 00:07:20,480 --> 00:07:21,950 that made up our bench. 114 00:07:21,950 --> 00:07:23,600 And of course, keep shooting. 115 00:07:23,870 --> 00:07:24,800 And there you go. 116 00:07:24,800 --> 00:07:29,690 You can see the spread of all the pellets coming out of our shotgun, and the bullet holes for each 117 00:07:29,690 --> 00:07:30,980 one of those pellets. 118 00:07:30,980 --> 00:07:32,990 So let me go ahead and shoot something else like this. 119 00:07:32,990 --> 00:07:39,650 If I shoot, there's all my bullets, and if I back up farther away, my bullets should be spread out 120 00:07:39,650 --> 00:07:39,890 more. 121 00:07:39,890 --> 00:07:41,180 So if I shoot again. 122 00:07:42,020 --> 00:07:43,700 And then let's go take a look. 123 00:07:43,700 --> 00:07:47,360 As you can see, the bullets spread out a lot more from my shotgun. 124 00:07:47,360 --> 00:07:48,230 Very cool. 125 00:07:50,910 --> 00:07:56,460 In the next lecture, we're going to continue adding new features to our guns, such as animations. 126 00:07:56,460 --> 00:07:58,680 So I'll see you in the next one.